#include "utils.h"

#ifndef BMP_H
#define BMP_H



using namespace std;

/**
 * \brief	Bitmap file descriptor. 
 *
 * \author	rsiancas
 * \date	3/28/2011
**/
class BMPFile
{
	
	BITMAPFILEHEADER header;				///< To store general information about the Bitmap Image File
	BITMAPINFOHEADER info_header;			///< To store detailed information about the bitmap image and define the pixel format
	DWORD *color_palette;					///< The color palette. To define colors used by the bitmap image data (Pixel Array)
	BYTE *bitmap_data;						///< To define the actual values of the pixels


public:
	BMPFile(){
		color_palette = 0;
		bitmap_data = 0;
	};
	~BMPFile(){
		delete color_palette;	
		delete bitmap_data;
	};

	/**
	 * \brief	Gets the bitmap information header.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \return	The bitmap information header.
	**/
	BITMAPINFOHEADER getBMPInfoHeader();
	/**
	 * \brief	Gets the bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \return	null if it fails, else the bitmap data.
	**/
	BYTE *getBitmapData();
	/**
	 * \brief	Gets the color palette.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \return	null if it fails, else the color palette.
	**/
	DWORD *getColorPalette();
	/**
	 * \brief	Sets a bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	bitmap	If non-null, the bitmap.
	 * \param	size		  	The size.
	**/
	void setBitmapData(BYTE *bitmap, int size);
	/**
	 * \brief	Creates a new BITMAPFILEHEADER using a size value passed as parameter.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param	bitmapSize	Size of the bitmap.
	**/
	void createNewBITMAPFILEHEADER(int bitmapSize);
	/**
	 * \brief	Gets a bitmapfileheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	in_stream	Stream to read data from.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool getBITMAPFILEHEADER(istream &in_stream);
	/**
	 * \brief	Puts a bitmapfileheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	out_stream	Stream to write data to.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool putBITMAPFILEHEADER(ostream &out_stream);
	/**
	 * \brief	Creates a new bitmapinfoheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param	width 	The width.
	 * \param	height	The height.
	**/
	void createNewBITMAPINFOHEADER(int width, int height);
	/**
	 * \brief	Gets a bitmapinfoheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	in_stream	Stream to read data from.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool getBITMAPINFOHEADER(istream &in_stream);
	/**
	 * \brief	Puts a bitmapinfoheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	out_stream	Stream to write data to.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool putBITMAPINFOHEADER(ostream &out_stream);
	/**
	 * \brief	Creates the new color palette.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	**/
	void createNewColorPalette();
	/**
	 * \brief	Gets a color palette.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	in_stream	Stream to read data from.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool getColorPalette(istream &in_stream);
	/**
	 * \brief	Print color palette.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	**/
	void printColorPalette();
	/**
	 * \brief	Puts a color palette.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	out_stream	Stream to write data to.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool putColorPalette(ostream &out_stream);
	/**
	 * \brief	Gets a bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	in_stream	Stream to read data from.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool getBitmapData(istream &in_stream);
	/**
	 * \brief	Print bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	**/
	void printBitmapData();
	/**
	 * \brief	Puts a bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	out_stream	Stream to write data to.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool putBitmapData(ostream &out_stream);
	/**
	 * \brief	Gets a pixel.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param	x	The x coordinate.
	 * \param	y	The y coordinate.
	**/
	void getPixel(int x, int y);
	/**
	 * \brief	Print bitmapfileheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	**/
	void printBITMAPFILEHEADER();
	/**
	 * \brief	Print bitmapinfoheader.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	**/
	void printBITMAPINFOHEADER();
	/**
	 * \brief	Gets a bitmap headers color palette bitmap data.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param	fileName	Filename of the file.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool getBMP_Headers_ColorPalette_BitmapData(const char *fileName);
	/**
	 * \brief	Builds a bitmap file.
	 *
	 * \author	rsiancas
	 * \date	3/25/2011
	 *
	 * \param [in,out]	out				The out.
	 * \param	ImageWidth				Width of the image.
	 * \param	ImageHeight				Height of the image.
	 * \param [in,out]	_ColorMap   	If non-null, the color map.
	 * \param [in,out]	ImageIndices	If non-null, the image indices.
	 *
	 * \return	true if it succeeds, false if it fails.
	**/
	bool buildBMPFile(ostream &out, int ImageWidth, int ImageHeight, ColorPaletteEntry *_ColorMap, BYTE *ImageIndices);
};

#endif